package com.quan.mall.service.impl;

import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.quan.commons.core.bean.R;
import com.quan.commons.core.biz.support.MyBaseServiceImpl;
import com.quan.commons.core.utils.PageUtils;
import com.quan.mall.commons.vo.*;
import com.quan.mall.entity.*;
import com.quan.mall.service.*;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import lombok.extern.slf4j.Slf4j;

import java.io.Serializable;
import java.util.*;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.stream.Collectors;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;

import com.quan.mall.mapper.PmsSpuMapper;
import org.springframework.transaction.annotation.Transactional;


@Slf4j
@Service
public class PmsSpuServiceImpl extends MyBaseServiceImpl<PmsSpuMapper, PmsSpu> implements PmsSpuService {

    @Autowired
	private PmsSpuMapper mapper;

    @Autowired
    private PmsSkuImagesService pmsSkuImagesService;

    @Autowired
    private PmsAttrService pmsAttrService;

    @Autowired
    private PmsSkuSaleAttrValueService pmsSkuSaleAttrValueService;

    @Autowired
    private PmsSpuDescInfoService pmsSpuDescInfoService;

    @Autowired
    private PmsSkuService pmsSkuService;

    @Autowired
    private PmsCategoryService pmsCategoryService;

    @Autowired
    private PmsBrandService pmsBrandService;

    @Autowired
    private PmsSpuAttrValueService pmsSpuAttrValueService;

    @Autowired
    private PmsSpuImgsService pmsSpuImgsService;

    @Autowired
    private WmsAgentInfoService wmsAgentInfoService;

    @Autowired
    private WmsWareSkuService wmsWareSkuService;

    @Transactional
    @Override
    public R saveGoodsInfo(PmsSpuVo vo) {
        // 保存SPU基本信息：pms_spu
        PmsSpu spu = new PmsSpu();
        BeanUtils.copyProperties(vo, spu);
        super.save(spu);

        // 保存SPU的详情：pms_spu_desc_info
        if(null != vo.getDecript()) {
            PmsSpuDescInfo decript = new PmsSpuDescInfo();
            decript.setSpuId(spu.getId());
            decript.setDecript(vo.getDecript());
            decript.setVideo(vo.getVideo());
            this.pmsSpuDescInfoService.save(decript);
        }

        // 保存SPU的轮播图：pms_spu_imgs
        if(null != vo.getImgs()) {
            final List<PmsSpuImgs> imgsList = vo.getImgs().stream().map(item -> {
                item.setSpuId(spu.getId());
                return item;
            }).collect(Collectors.toList());
            this.pmsSpuImgsService.saveBatch(imgsList);
        }

        // 保存spu的基本规格参数：pms_spu_attr_value
        List<BaseAttrsVo> baseAttrs = vo.getBaseAttrs();
        if(null != baseAttrs && !baseAttrs.isEmpty()) {
            List<PmsSpuAttrValue> collect = baseAttrs.stream().map(attr -> {
                PmsSpuAttrValue spuAttrValue = new PmsSpuAttrValue();
                spuAttrValue.setAttrId(attr.getAttrId());

                //查询attr属性名
                PmsAttr pmsAttr = pmsAttrService.getById(attr.getAttrId());

                spuAttrValue.setAttrName(pmsAttr.getAttrName());
                spuAttrValue.setAttrValue(attr.getAttrValues());
                spuAttrValue.setQuickShow(attr.getShowDesc());
                spuAttrValue.setSpuId(spu.getId());
                spuAttrValue.setValueType(pmsAttr.getValueType());
                return spuAttrValue;
            }).collect(Collectors.toList());
            this.pmsSpuAttrValueService.saveBatch(collect);
        }

        // 保存当前spu对应的所有sku信息：pms_sku
        final List<PmsSkuVo> skus = vo.getSkus();
        if(skus != null && !skus.isEmpty()) {

            skus.forEach(skuItem -> {
                // 1）、sku的基本信息:pms_sku
                PmsSku sku = new PmsSku();
                BeanUtils.copyProperties(skuItem, sku);
                sku.setCateId(vo.getCateId());
                sku.setSpuId(spu.getId());
                sku.setAttrs(skuItem.getSpecAttrs() != null && skuItem.getSpecAttrs().size() > 0 ? JSON.toJSONString(skuItem.getSpecAttrs()) : "[{'attrId':0,'attrName':'默认','attrValue':'统一规格'}]");
                sku.setDescar(skuItem.getSpecDescar() != null && skuItem.getSpecDescar().size() > 0 ? JSON.toJSONString(skuItem.getSpecDescar()) : "['默认']");
                this.pmsSkuService.save(sku);

                final List<WmsAgentInfo> agentInfoList = this.wmsAgentInfoService.list();
                // 初始化库存（代理商）
                if(null != agentInfoList && agentInfoList.size() > 0) {
                    for (WmsAgentInfo agent : agentInfoList) {
                        WmsWareSku wareSku = new WmsWareSku();
                        wareSku.setAgentId(agent.getId());
                        wareSku.setSkuId(sku.getId());
                        wareSku.setSkuName(sku.getSkuName());
                        wareSku.setSkuAttr(sku.getDescar());
                        wareSku.setStock(0);
                        this.wmsWareSkuService.save(wareSku);
                    }
                }


                // 2）、sku的销售属性：pms_sku_sale_attr_value
                final List<PmsSkuSaleAttrValueVo> attrs = skuItem.getSpecAttrs();
                if(null != attrs && !attrs.isEmpty()) {
                    final List<PmsSkuSaleAttrValue> collect = attrs.stream().map(item -> {
                        PmsSkuSaleAttrValue saleAttrValue = new PmsSkuSaleAttrValue();
                        BeanUtils.copyProperties(item, saleAttrValue);
                        saleAttrValue.setSkuId(sku.getId());
                        return saleAttrValue;
                    }).collect(Collectors.toList());
                    this.pmsSkuSaleAttrValueService.saveBatch(collect);
                }

            });

            vo.getSkus().stream().forEach(System.out::println);
        }

        return R.ok();
    }

    @Transactional
    @Override
    public R updateGoodsInfo(PmsSpuVo vo) {
        // 删除SPU轮播图
        this.pmsSpuImgsService.remove(new QueryWrapper<PmsSpuImgs>().eq("spu_id", vo.getId()));
        // 删除SPU详情
        this.pmsSpuDescInfoService.remove(new QueryWrapper<PmsSpuDescInfo>().eq("spu_id", vo.getId()));
        // 删除SKU相关信息
        this.pmsSkuService.remove(new QueryWrapper<PmsSku>().eq("spu_id", vo.getId()));
        this.pmsSkuSaleAttrValueService.remove(new QueryWrapper<PmsSkuSaleAttrValue>().eq("sku_id", vo.getId()));
        this.pmsSkuImagesService.remove(new QueryWrapper<PmsSkuImages>().eq("sku_id", vo.getId()));
        // 删除SPU基本规格参数
        this.pmsSpuAttrValueService.remove(new QueryWrapper<PmsSpuAttrValue>().eq("spu_id", vo.getId()));

        // 修改SPU基本信息
        PmsSpu spu = new PmsSpu();
        BeanUtils.copyProperties(vo, spu);
        super.updateById(spu);

        // 保存SPU的详情：pms_spu_desc_info
        if(null != vo.getDecript()) {
            PmsSpuDescInfo decript = new PmsSpuDescInfo();
            decript.setSpuId(spu.getId());
            decript.setDecript(vo.getDecript());
            decript.setVideo(vo.getVideo());
            this.pmsSpuDescInfoService.save(decript);
        }

        // 保存SPU的轮播图：pms_spu_imgs
        if(null != vo.getImgs()) {
            final List<PmsSpuImgs> imgsList = vo.getImgs().stream().map(item -> {
                item.setSpuId(vo.getId());
                return item;
            }).collect(Collectors.toList());
            this.pmsSpuImgsService.saveBatch(imgsList);
        }

        // 保存spu的基本规格参数：pms_spu_attr_value
        List<BaseAttrsVo> baseAttrs = vo.getBaseAttrs();
        if(null != baseAttrs && !baseAttrs.isEmpty()) {
            List<PmsSpuAttrValue> collect = baseAttrs.stream().map(attr -> {
                PmsSpuAttrValue spuAttrValue = new PmsSpuAttrValue();
                spuAttrValue.setAttrId(attr.getAttrId());

                //查询attr属性名
                PmsAttr pmsAttr = pmsAttrService.getById(attr.getAttrId());

                spuAttrValue.setAttrName(pmsAttr.getAttrName());
                spuAttrValue.setAttrValue(attr.getAttrValues());
                spuAttrValue.setQuickShow(attr.getShowDesc());
                spuAttrValue.setSpuId(spu.getId());
                spuAttrValue.setValueType(pmsAttr.getValueType());
                return spuAttrValue;
            }).collect(Collectors.toList());
            this.pmsSpuAttrValueService.saveBatch(collect);
        }


        // 保存当前spu对应的所有sku信息：pms_sku
        final List<PmsSkuVo> skus = vo.getSkus();
        if(skus != null && !skus.isEmpty()) {

            skus.forEach(skuItem -> {
                // 1）、sku的基本信息:pms_sku
                PmsSku sku = new PmsSku();
                BeanUtils.copyProperties(skuItem, sku);

                sku.setCateId(vo.getCateId());
                sku.setSpuId(vo.getId());
                sku.setAttrs(skuItem.getSpecAttrs() != null && skuItem.getSpecAttrs().size() > 0 ? JSON.toJSONString(skuItem.getSpecAttrs()) : "[{'attrId':0,'attrName':'默认','attrValue':'统一规格'}]");
                sku.setDescar(skuItem.getSpecDescar() != null && skuItem.getSpecDescar().size() > 0 ? JSON.toJSONString(skuItem.getSpecDescar()) : "['默认']");
                this.pmsSkuService.save(sku);

                // 2）、sku的销售属性：pms_sku_sale_attr_value
                final List<PmsSkuSaleAttrValueVo> attrs = skuItem.getSpecAttrs();
                if(null != attrs && !attrs.isEmpty()) {
                    final List<PmsSkuSaleAttrValue> collect = attrs.stream().map(item -> {
                        PmsSkuSaleAttrValue saleAttrValue = new PmsSkuSaleAttrValue();
                        BeanUtils.copyProperties(item, saleAttrValue);
                        saleAttrValue.setSkuId(sku.getId());
                        return saleAttrValue;
                    }).collect(Collectors.toList());
                    this.pmsSkuSaleAttrValueService.saveBatch(collect);
                }

            });

        }

        return R.ok();
    }

	@Override
    public List<PmsSpuVo> queryList(PageUtils pageUtils, PmsSpuVo vo) {
        QueryWrapper<PmsSpu> queryWrapper = new QueryWrapper<PmsSpu>(vo);

        List<PmsSpu> list = super.list(pageUtils, queryWrapper);
        List<PmsSpuVo> collect = list.stream().map(item -> {
            PmsSpuVo bean = new PmsSpuVo();
            BeanUtils.copyProperties(item, bean);
            return bean;
        }).collect(Collectors.toList());

        return collect;
    }

    @Override
    public PageUtils queryPage(PageUtils pageUtils, PmsSpuVo vo) {
        QueryWrapper<PmsSpu> queryWrapper = new QueryWrapper<PmsSpu>(vo);

        if(StringUtils.isNotBlank(vo.getKeyword())) {
            queryWrapper.and(w -> {
                w.like("title", vo.getKeyword());
            });
        }
        if(StringUtils.isNotEmpty(vo.getName())) {
            queryWrapper.and(w -> {
                w.like("title", vo.getName());
            });
        }

        //// min 大于 0
        //if (null != vo.getPriceMin() && vo.getPriceMin().compareTo(BigDecimal.ZERO) == 1) {
        //    queryWrapper.ge("price",vo.getPriceMin());
        //}
        //
        //// max 大于 0
        //if (null != vo.getPriceMin() && vo.getPriceMax().compareTo(BigDecimal.ZERO) == 1) {
        //    queryWrapper.le("price",vo.getPriceMax());
        //}

        // 查询库存预警商品
        if(vo.isQueryStockWarn()) {

        }

        final IPage<PmsSpu> page = super.selectPage(pageUtils, queryWrapper);

        PageUtils ps = new PageUtils(page);

        final List<PmsSpu> records = page.getRecords();

        List<PmsSpuVo> collect = records.stream().map((item) -> {
            PmsSpuVo spuVo = new PmsSpuVo();
            BeanUtils.copyProperties(item, spuVo);

            // 分类
            //PmsCategory category = this.pmsCategoryService.getById(spuVo.getCateId());
            //if (category != null) {
            //    spuVo.setCategoryName(category.getName());
            //}

            // 品牌
            //final PmsBrand brand = this.pmsBrandService.getById(spuVo.getBrandId());
            //if(null != brand) {
            //    spuVo.setBrandName(brand.getName());
            //}

            // sku
            final List<PmsSku> skus = this.pmsSkuService.list(new QueryWrapper<PmsSku>().eq("spu_id", item.getId()));
            final List<PmsSkuVo> skusVo = skus.stream().map(sku -> {
                PmsSkuVo skuVo = new PmsSkuVo();
                BeanUtils.copyProperties(sku, skuVo);

                return skuVo;
            }).collect(Collectors.toList());
            spuVo.setSkus(skusVo);

            // 取出sku中的最低价格最高价，总库存量，总销量
            if(null != skusVo && skusVo.size() != 0) {
                if(skusVo.size() > 1) {
                    // 最低价
                    final Optional<PmsSkuVo> min = skusVo.stream().min(Comparator.comparing(PmsSkuVo::getSalePrice));
                    // 最高价
                    final Optional<PmsSkuVo> max = skusVo.stream().max(Comparator.comparing(PmsSkuVo::getSalePrice));

                    // 总库存量
                    final int totalStock = skusVo.stream().mapToInt(PmsSkuVo::getStockNum).sum();
                    // 总销量
                    final int totalSalesVolume = skusVo.stream().mapToInt(PmsSkuVo::getSaleNum).sum();

                    // 最小价格
                    spuVo.setMinPrice(min.get().getSalePrice());
                    // 最大价格
                    spuVo.setMaxPrice(max.get().getSalePrice());

                    // 总库存
                    spuVo.setTotalStock(totalStock);
                    // 总销量
                    spuVo.setTotalSaleNum(totalSalesVolume);
                    // 当前总库存
                    spuVo.setCurTotalStock(totalStock - totalSalesVolume);
                } else {
                    // 价格
                    spuVo.setPrice(skusVo.get(0).getSalePrice());
                    // 总销量
                    spuVo.setTotalStock(skusVo.get(0).getStockNum() - skusVo.get(0).getSaleNum());
                }
            }

            return spuVo;
        }).collect(Collectors.toList());

        // 过滤出库存预警的商品，注：无法参与分页
        if(vo.isQueryStockWarn()) {
            collect = collect.stream().filter(item -> item.getTotalStock() < item.getStockWarn()).map(item -> item).collect(Collectors.toList());
        }

        ps.setRecords(collect);
        return ps;
    }

    @Override
    public PmsSpuVo getGoodsInfo(PmsSpuVo vo) {
        PmsSpuVo pmsSpuVo = new PmsSpuVo();
        final PmsSpu spu = super.getById(vo.getId());
        BeanUtils.copyProperties(spu, pmsSpuVo);

        // 分类信息
        //pmsSpuVo.setCategoryPath(pmsCategoryService.findCategoryPath(spu.getCateId()));
        //pmsSpuVo.setCategoryName(pmsCategoryService.getById(spu.getCateId()).getName());

        // 轮播图
        pmsSpuVo.setImgs(this.pmsSpuImgsService.list(new QueryWrapper<PmsSpuImgs>().eq("spu_id", vo.getId())));

        // 商品详情信息
        final PmsSpuDescInfo spuDescInfo = this.pmsSpuDescInfoService.getOne(new QueryWrapper<PmsSpuDescInfo>().eq("spu_id", vo.getId()), false);
        if (spuDescInfo != null) {
            pmsSpuVo.setDecript(spuDescInfo.getDecript());
            pmsSpuVo.setVideo(spuDescInfo.getVideo());
        }


        // 商品基本规格属性
        //final List<PmsSpuAttrValue> spuAttrValueList = this.pmsSpuAttrValueService.list(new QueryWrapper<PmsSpuAttrValue>().eq("spu_id", vo.getId()));
        //pmsSpuVo.setSpuAttrValues(spuAttrValueList);

        // 商品SKU信息
        final List<PmsSku> skus = this.pmsSkuService.list(new QueryWrapper<PmsSku>().eq("spu_id", spu.getId()));
        final List<PmsSkuVo> collect = skus.stream().map(item -> {
            PmsSkuVo psv = new PmsSkuVo();
            BeanUtils.copyProperties(item, psv);
            return psv;
        }).collect(Collectors.toList());
        pmsSpuVo.setSkus(collect);

        // 取出sku中的最低价格最高价，总库存量，总销量
        if(null != collect && collect.size() != 0) {
            if(collect.size() > 1) {
                // 最低价
                final Optional<PmsSkuVo> min = collect.stream().min(Comparator.comparing(PmsSkuVo::getSalePrice));
                // 最高价
                final Optional<PmsSkuVo> max = collect.stream().max(Comparator.comparing(PmsSkuVo::getSalePrice));

                // 总库存量
                final int totalStock = collect.stream().mapToInt(PmsSkuVo::getStockNum).sum();
                // 总销量
                final int totalSalesVolume = collect.stream().mapToInt(PmsSkuVo::getSaleNum).sum();

                // 最小价格
                pmsSpuVo.setMinPrice(min.get().getSalePrice());
                // 最大价格
                pmsSpuVo.setMaxPrice(max.get().getSalePrice());

                // 总库存
                pmsSpuVo.setTotalStock(totalStock);
                // 总销量
                pmsSpuVo.setTotalSaleNum(totalSalesVolume);
                // 当前总库存
                pmsSpuVo.setCurTotalStock(totalStock - totalSalesVolume);
            } else {
                // 价格
                pmsSpuVo.setPrice(collect.get(0).getSalePrice());

                // 总库存
                pmsSpuVo.setTotalStock(collect.get(0).getStockNum());
                // 总销量
                pmsSpuVo.setTotalSaleNum(collect.get(0).getSaleNum());
                // 当前总库存
                pmsSpuVo.setCurTotalStock(collect.get(0).getStockNum() - collect.get(0).getSaleNum());

            }
        }

        return pmsSpuVo;
    }

    @Override
    public void changeStatus(Long id, Integer status) {
        UpdateWrapper<PmsSpu> updateWrapper = new UpdateWrapper<PmsSpu>();
        updateWrapper.eq("id", id);
        updateWrapper.set("status", status);
        super.update(updateWrapper);
    }

    @Override
    public void changeIsBest(Long id, Integer isBest) {
        UpdateWrapper<PmsSpu> updateWrapper = new UpdateWrapper<PmsSpu>();
        updateWrapper.eq("id", id);
        updateWrapper.set("is_best", isBest);
        super.update(updateWrapper);
    }

    @Override
    public void changeIsHot(Long id, Integer isHot) {
        UpdateWrapper<PmsSpu> updateWrapper = new UpdateWrapper<PmsSpu>();
        updateWrapper.eq("id", id);
        updateWrapper.set("is_hot", isHot);
        super.update(updateWrapper);
    }

    @Override
    public void changeIsNew(Long id, Integer isNew) {
        UpdateWrapper<PmsSpu> updateWrapper = new UpdateWrapper<PmsSpu>();
        updateWrapper.eq("id", id);
        updateWrapper.set("is_new", isNew);
        super.update(updateWrapper);
    }

    @Override
    public void changeIsRecom(Long id, Integer isRecom) {
        UpdateWrapper<PmsSpu> updateWrapper = new UpdateWrapper<PmsSpu>();
        updateWrapper.eq("id", id);
        updateWrapper.set("is_recom", isRecom);
        super.update(updateWrapper);
    }

    @Override
    public PmsSpuVo getGoodsCount() {
        final List<PmsSpu> list = super.list();

        // 售卖中的商品数量
        final long saleCount = list.stream().filter(p -> p.getStatus() == 1).count();

        // 仓库中的商品数量
        final long stockCount = list.stream().filter(p -> p.getStatus() == 2).count();

        // 库存预警商品数量累加
        AtomicInteger stockWarnCount = new AtomicInteger();

        // 库存预警的商品数量
        list.stream().map(item -> {

            if(item.getStockWarn() > 0) {
                final List<PmsSku> skus = this.pmsSkuService.list(new QueryWrapper<PmsSku>().eq("spu_id", item.getId()));

                // 总库存量
                final int totalStock = skus.stream().mapToInt(PmsSku::getStockNum).sum();
                // 总销量
                final int totalSalesVolume = skus.stream().mapToInt(PmsSku::getSaleNum).sum();

                // 总库存小于预警库存量则++
                if(totalStock<item.getStockWarn()) {
                    stockWarnCount.getAndIncrement();
                }
            }
            return null;
        }).collect(Collectors.toList());

        PmsSpuVo spuVo = new PmsSpuVo();
        spuVo.setSaleCount(saleCount);
        spuVo.setStockCount(stockCount);
        spuVo.setStockWarnCount(stockWarnCount.get());

        return spuVo;
    }

    @Override
    public boolean removeByIds(Collection<? extends Serializable> idList) {

        // 删除SPU轮播图
        this.pmsSpuImgsService.remove(new QueryWrapper<PmsSpuImgs>().in("spu_id", idList));
        // 删除SPU详情
        this.pmsSpuDescInfoService.remove(new QueryWrapper<PmsSpuDescInfo>().in("spu_id", idList));
        // 删除SKU相关信息
        this.pmsSkuService.remove(new QueryWrapper<PmsSku>().in("spu_id", idList));
        this.pmsSkuSaleAttrValueService.remove(new QueryWrapper<PmsSkuSaleAttrValue>().in("sku_id", idList));
        this.pmsSkuImagesService.remove(new QueryWrapper<PmsSkuImages>().in("sku_id", idList));
        // 删除SPU基本规格参数
        this.pmsSpuAttrValueService.remove(new QueryWrapper<PmsSpuAttrValue>().in("spu_id", idList));


        return super.removeByIds(idList);
    }
}